package com.qianzhu8.kfc.boot.util;

import com.qianzhu8.kfc.boot.request.BaseRequest;
import lombok.SneakyThrows;
import lombok.experimental.UtilityClass;

import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;

import static com.qianzhu8.kfc.boot.constant.SignConstants.EXCLUDE_SIGN_FIELDS;

/**
 * 签名工具类
 *
 * @author xuyanjun
 * @date 2020/4/10
 */
@UtilityClass
public class SignUtils {

    /**
     * 构造签名map
     *
     * @param request request
     * @return 签名map
     */
    @SneakyThrows
    public static Map<String, String> buildSignMap(BaseRequest request){
        List<Field> fields = BeanUtils.getAllFields(request.getClass());
        Map<String, String> signMap = new HashMap<>(8);
        for (Field field : fields) {
            if (!EXCLUDE_SIGN_FIELDS.contains(field.getName())) {
                field.setAccessible(true);
                signMap.put(field.getName(), String.valueOf(field.get(request)));
            }
        }

        return signMap;
    }

    /**
     * 生成签名
     *
     * @param map    要验签的对象map
     * @param secret 密钥
     * @return 签名
     */
    @SneakyThrows
    public static String generateSign(Map<String, String> map, String secret) {
        Map<String, String> reqMap = new TreeMap<>(map);

        StringBuilder paramBuilder = new StringBuilder();
        reqMap.forEach((k, v) ->
                paramBuilder.append(String.format("%s=%s&", k, v == null ? "" : v))
        );
        String paramStr = paramBuilder.substring(0, paramBuilder.length()-1);
        paramStr = paramStr + secret;

        return Md5Utils.md5(paramStr);
    }
}
